package com.ibeeking.found.org.cp.rest.service.impl;

import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.util.ObjectUtil;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.ibeeking.found.common.config.prop.FileOssProp;
import com.ibeeking.found.common.constants.DefaultPathConstant;
import com.ibeeking.found.common.entity.AreaDTO;
import com.ibeeking.found.common.entity.EmployeeDTO;
import com.ibeeking.found.common.entity.query.EmployeeFeignQuery;
import com.ibeeking.found.common.enums.PublishStatusEnum;
import com.ibeeking.found.common.enums.SexEnum;
import com.ibeeking.found.common.utils.DataUtils;
import com.ibeeking.found.common.utils.DateUtils;
import com.ibeeking.found.common.utils.UrlUtils;
import com.ibeeking.found.common.utils.UserUtils;
import com.ibeeking.found.org.api.common.param.EmployeeFeignParam;
import com.ibeeking.found.org.cp.rest.config.prop.EmployeeConfigProp;
import com.ibeeking.found.org.cp.rest.service.IEmployeeService;
import com.ibeeking.found.org.service.common.bo.EmployeeBO;
import com.ibeeking.found.org.service.common.constants.RedisKeyConstant;
import com.ibeeking.found.org.service.common.dos.DepartmentDO;
import com.ibeeking.found.org.service.common.dos.EmployeeDO;
import com.ibeeking.found.org.service.common.dos.OrgPositionDO;
import com.ibeeking.found.org.service.common.enums.EmployeeStatusEnum;
import com.ibeeking.found.org.service.common.enums.QrCodeTypeEnum;
import com.ibeeking.found.org.service.common.param.EmployeeExtendFieldParam;
import com.ibeeking.found.org.service.common.param.EmployeeParam;
import com.ibeeking.found.org.service.common.param.QrCodeParam;
import com.ibeeking.found.org.service.common.query.EmployeePageQuery;
import com.ibeeking.found.org.service.common.query.EmployeeQuery;
import com.ibeeking.found.org.service.common.vo.DepartmentTreeVO;
import com.ibeeking.found.org.service.common.vo.EmployeeStatusVO;
import com.ibeeking.found.org.service.common.vo.EmployeeVO;
import com.ibeeking.found.org.service.mapper.DepartmentMapper;
import com.ibeeking.found.org.service.mapper.EmployeeMapper;
import com.ibeeking.found.org.service.mapper.OrgPositionMapper;
import com.ibeeking.gmc.global.api.feign.GlobalDictFeignClient;
import com.ibeeking.nematos.constants.enums.LogClassifyEnum;
import com.ibeeking.nematos.core.utils.SpringBeanUtil;
import com.ibeeking.nematos.exception.BusinessException;
import com.ibeeking.nematos.log.utils.LogUtils;
import com.ibeeking.nematos.qrcode.Codectx;
import com.ibeeking.nematos.qrcode.qrcode.QrcodeConfig;
import com.ibeeking.nematos.qrcode.qrcode.SimpleQrcodeGenerator;
import com.ibeeking.nematos.redis.annotation.CacheEvict;
import com.ibeeking.nematos.redis.utils.RedisUtils;
import com.ibeeking.nematos.utils.bean.BeanUtil;
import com.ibeeking.nematos.utils.data.Collections3;
import com.ibeeking.nematos.utils.data.TreeFastUtils;
import com.ibeeking.nematos.utils.id.IdGen;
import com.ibeeking.nematos.utils.id.IdGenerator;
import com.ibeeking.nematos.utils.json.JsonUtils;
import com.ibeeking.nematos.utils.result.ResponseResult;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.OutputStream;
import java.time.LocalDateTime;
import java.util.*;
import java.util.stream.Collectors;
/**
 * @ClassName EmployeeServiceImpl
 * @Description
 * @Author ibeeking
 * @Date 2021-01-29 14:48
 **/
@Service
public class EmployeeServiceImpl extends ServiceImpl<EmployeeMapper, EmployeeDO> implements IEmployeeService {

    @Resource
    private EmployeeMapper employeeMapper;

    @Resource
    private DepartmentMapper departmentMapper;

    @Resource
    private OrgPositionMapper orgPositionMapper;

    @Resource
    private GlobalDictFeignClient globalDictFeignClient;

    @Resource
    private EmployeeConfigProp configProp;

    @Resource
    private FileOssProp fileOssProp;

    @Resource
    private RedisUtils redisUtils;

    @Override
    public List<EmployeeVO> list(EmployeeQuery query) {
        if(query.getDepartmentId() != null){
            List<Long> departmentIds = getAllDepartmentIdsByPId(query.getDepartmentId());
            query.setDepartmentIds(departmentIds);
        }
        List<EmployeeVO> resultVOS = new ArrayList<>();
        List<EmployeeDO> entityDOS = employeeMapper.selectList(new LambdaQueryWrapper<EmployeeDO>()
                .eq(query.getId()!=null ,EmployeeDO::getId, query.getId())
                .in(Collections3.isNotEmpty(query.getDepartmentIds()),EmployeeDO::getDepartmentId,query.getDepartmentIds())
                .eq(query.getPositionId()!=null ,EmployeeDO::getPositionId, query.getPositionId())
                .eq(query.getGender()!=null ,EmployeeDO::getGender, query.getGender())
                .eq(StringUtils.isNotEmpty(query.getCode()),EmployeeDO::getCode, query.getCode())
                .like(StringUtils.isNotEmpty(query.getName()),EmployeeDO::getName, query.getName())
                .eq(query.getStatus()!=null ,EmployeeDO::getStatus, query.getStatus())
                .orderByDesc(EmployeeDO::getCreateTime));
        if(Collections3.isNotEmpty(entityDOS)){
            List<DepartmentDO> departmentDOList = departmentMapper.selectList(new LambdaQueryWrapper<DepartmentDO>().eq(DepartmentDO::getPublishStatus,PublishStatusEnum.ENABLE.getValue()));
            Map<Long, String> departmentNameMaps = Collections3.isNotEmpty(departmentDOList)?departmentDOList.parallelStream().collect(Collectors.toMap(DepartmentDO::getId, DepartmentDO::getName, (o, n) -> o)):null;

            List<OrgPositionDO> orgPositionDOList = orgPositionMapper.selectList(new LambdaQueryWrapper<OrgPositionDO>().eq(OrgPositionDO::getPublishStatus,PublishStatusEnum.ENABLE.getValue()));
            Map<Long, String> orgPositionNameMaps = Collections3.isNotEmpty(orgPositionDOList)?orgPositionDOList.parallelStream().collect(Collectors.toMap(OrgPositionDO::getId, OrgPositionDO::getName, (o, n) -> o)):null;
            Map<Long, Long> orgPositionJobMaps = Collections3.isNotEmpty(orgPositionDOList)?orgPositionDOList.parallelStream().collect(Collectors.toMap(OrgPositionDO::getId, OrgPositionDO::getJobId, (o, n) -> o)):null;

            resultVOS = entityDOS.stream().map(s->{
                EmployeeVO entityVO = BeanUtil.convertBean(s, EmployeeVO.class);
                entityVO.setDepartmentName(departmentNameMaps!=null?departmentNameMaps.get(s.getDepartmentId()):"");
                entityVO.setPositionName(orgPositionNameMaps!=null?orgPositionNameMaps.get(s.getPositionId()):"");
                entityVO.setJobId(orgPositionJobMaps!=null?orgPositionJobMaps.get(s.getPositionId()):null);
                entityVO.setStatusDesc(EmployeeStatusEnum.getDescByCode(s.getStatus()));
                entityVO.setGenderDesc(SexEnum.getDescByCode(s.getGender()));
                return entityVO;
            }).collect(Collectors.toList());
        }
        return resultVOS;
    }

    @Override
    public Page<EmployeeVO> pageList(EmployeePageQuery pageQuery) {
        if(pageQuery.getDepartmentId() != null){
            List<Long> departmentIds = getAllDepartmentIdsByPId(pageQuery.getDepartmentId());
            pageQuery.setDepartmentIds(departmentIds);
        }
        LambdaQueryWrapper<EmployeeDO> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(pageQuery.getId() != null, EmployeeDO::getId, pageQuery.getId())
                .eq(pageQuery.getId()!=null ,EmployeeDO::getId, pageQuery.getId())
                .in(Collections3.isNotEmpty(pageQuery.getDepartmentIds()),EmployeeDO::getDepartmentId,pageQuery.getDepartmentIds())
                .eq(pageQuery.getPositionId()!=null ,EmployeeDO::getPositionId, pageQuery.getPositionId())
                .eq(pageQuery.getGender()!=null ,EmployeeDO::getGender, pageQuery.getGender())
                .eq(StringUtils.isNotEmpty(pageQuery.getCode()),EmployeeDO::getCode, pageQuery.getCode())
                .like(StringUtils.isNotEmpty(pageQuery.getName()),EmployeeDO::getName, pageQuery.getName())
                .eq(pageQuery.getStatus()!=null ,EmployeeDO::getStatus, pageQuery.getStatus())
                .orderByDesc(EmployeeDO::getCreateTime);

        Page<EmployeeDO> entityDOPages = employeeMapper.selectPage(new Page<EmployeeDO>(pageQuery.getPageNum(), pageQuery.getPageSize()), wrapper);
        if(entityDOPages!=null && entityDOPages.getSize() > 0) {
            Page<EmployeeVO> entityVOPage = BeanUtil.convertPage(entityDOPages, EmployeeVO.class);
            List<EmployeeDO> entityDOList = entityDOPages.getRecords();

            List<DepartmentDO> departmentDOList = departmentMapper.selectList(new LambdaQueryWrapper<DepartmentDO>().eq(DepartmentDO::getPublishStatus, PublishStatusEnum.ENABLE.getValue()));
            Map<Long, String> departmentNameMaps = Collections3.isNotEmpty(departmentDOList) ? departmentDOList.parallelStream().collect(Collectors.toMap(DepartmentDO::getId, DepartmentDO::getName, (o, n) -> o)) : null;
            List<OrgPositionDO> orgPositionDOList = orgPositionMapper.selectList(new LambdaQueryWrapper<OrgPositionDO>().eq(OrgPositionDO::getPublishStatus, PublishStatusEnum.ENABLE.getValue()));
            Map<Long, String> orgPositionNameMaps = Collections3.isNotEmpty(orgPositionDOList) ? orgPositionDOList.parallelStream().collect(Collectors.toMap(OrgPositionDO::getId, OrgPositionDO::getName, (o, n) -> o)) : null;
            Map<Long, Long> orgPositionJobMaps = Collections3.isNotEmpty(orgPositionDOList)?orgPositionDOList.parallelStream().collect(Collectors.toMap(OrgPositionDO::getId, OrgPositionDO::getJobId, (o, n) -> o)):null;

            List<EmployeeVO> resultVOList = entityDOList.stream().map(s -> {
                EmployeeVO entityVO = BeanUtil.convertBean(s, EmployeeVO.class);
                entityVO.setDepartmentName(departmentNameMaps!=null?departmentNameMaps.get(s.getDepartmentId()):"");
                entityVO.setPositionName(orgPositionNameMaps!=null?orgPositionNameMaps.get(s.getPositionId()):"");
                entityVO.setJobId(orgPositionJobMaps!=null?orgPositionJobMaps.get(s.getPositionId()):null);
                entityVO.setStatusDesc(EmployeeStatusEnum.getDescByCode(s.getStatus()));
                entityVO.setGenderDesc(SexEnum.getDescByCode(s.getGender()));
                return entityVO;
            }).collect(Collectors.toList());
            entityVOPage.setRecords(resultVOList);
            return entityVOPage;
        }
        return new Page<>();
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public Boolean add(EmployeeParam param) {
        this.checkUnique(param);
        EmployeeDO entityDO = BeanUtil.convertBean(param, EmployeeDO.class);
        entityDO.setId(IdGenerator.getId());
        entityDO.setCreateBy(UserUtils.getUserId());
        entityDO.setCreateTime(LocalDateTime.now());
        entityDO.setModifyTime(LocalDateTime.now());
        return employeeMapper.insert(entityDO) > 0;
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public Boolean modify(EmployeeParam param) {
        this.checkUnique(param);
        EmployeeDO entityDO = BeanUtil.convertBean(param, EmployeeDO.class);
        entityDO.setModifyBy(UserUtils.getUserId());
        entityDO.setModifyTime(LocalDateTime.now());
        return employeeMapper.updateById(entityDO) > 0;
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public Boolean feignAddorUpdate(EmployeeFeignParam param) {
        LambdaQueryWrapper<EmployeeDO> queryWrapper = new LambdaQueryWrapper<EmployeeDO>()
                .eq(param.getId() != null, EmployeeDO::getId, param.getId())
                .or()
                .eq(StringUtils.isNotEmpty(param.getName()),EmployeeDO::getName, param.getName());
        EmployeeDO dos = employeeMapper.selectOne(queryWrapper);
        if(dos != null) {
            EmployeeDO entityDO = BeanUtil.convertBean(param, EmployeeDO.class);
            entityDO.setModifyBy(UserUtils.getUserId());
            entityDO.setModifyTime(LocalDateTime.now());
            return employeeMapper.updateById(entityDO) > 0;
        }else{
            EmployeeDO entityDO = BeanUtil.convertBean(param, EmployeeDO.class);
            entityDO.setId(IdGenerator.getId());
            entityDO.setCreateBy(UserUtils.getUserId());
            entityDO.setCreateTime(LocalDateTime.now());
            entityDO.setModifyTime(LocalDateTime.now());
            return employeeMapper.insert(entityDO) > 0;
        }
    }

    /**
     * 会员信息(头像/昵称/性别/出生日期/车牌号)修改
     *
     * @param param
     * @return
     */
    @Transactional(rollbackFor = Exception.class)
    @Override
    public Boolean infoModify(EmployeeParam param) {
        Long id = param.getId();
        String headImageUrl = param.getAvatar();
        String name = param.getName();
        Integer sex = param.getGender();
        String birthday = param.getBirthday();
        String idCardNo = param.getIdCardNo();
        EmployeeDO up = BeanUtil.convertBean(param, EmployeeDO.class);
        up.setId(id);
        int count = 0;
        Long taskId = 0L;
        if (StringUtils.isNotBlank(headImageUrl)) {
            up.setAvatar(UrlUtils.removeUrlDomainName(headImageUrl));
            count++;
        }
        //从身份证号中获取出生日期,如果之前没有出生日期数据,就修改
        if (StringUtils.isNotBlank(idCardNo)) {
            EmployeeBO memberInfoOld = getBean().selectById(id);
            if (memberInfoOld != null && StringUtils.isBlank(memberInfoOld.getBirthday())) {
                String birtByIdNo = getBirtByIdNo(idCardNo);
                Date birthdayDate;
                try {
                    birthdayDate = DateUtils.parseDate(birtByIdNo, DateUtils.YYYY_MM_DD);
                } catch (Exception e) {
                    throw BusinessException.create("生日格式异常!");
                }
                if (DateUtils.compareDate(birthdayDate, new Date())) {
                    throw BusinessException.create("身份证中的出生日期必须小于当前日期!");
                }
                up.setBirthday(DateUtils.dateToLocalDate(birthdayDate));
            }
        }
        return getBean().updateEmployeeById(up);

    }

    @Transactional(rollbackFor = Exception.class)
    @CacheEvict(cacheName = RedisKeyConstant.EMPLOYEE_PREFIX, key = "#employeeDO.id")
    @Override
    public Boolean updateEmployeeById(EmployeeDO entityDO) {
        if (entityDO == null) {
            return false;
        }
        return employeeMapper.updateById(entityDO) > 0;
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public void modifyAddr(Long employeeId, String provinceCode, String cityCode, String regionCode, String streetCode, String detailAddress) {
        LambdaUpdateWrapper<EmployeeDO> updateWrapper = new LambdaUpdateWrapper<EmployeeDO>().eq(EmployeeDO::getId, employeeId)
                .set(EmployeeDO::getProvinceCode, provinceCode)
                .set(EmployeeDO::getCityCode, cityCode)
                .set(EmployeeDO::getRegionCode, regionCode)
                .set(EmployeeDO::getStreetCode, streetCode)
                .set(EmployeeDO::getAddress, detailAddress);
        employeeMapper.update(null, updateWrapper);
    }

    @Override
    public JSONObject queryEmployeeExtendField(Long employeeId) {
        JSONObject result = new JSONObject();
        if (ObjectUtil.isNull(employeeId)) {
            return result;
        }
        EmployeeDO memberInfoDO = employeeMapper.selectById(employeeId);
        String extendedInformation = memberInfoDO.getExtendField();
        if (StringUtils.isNotBlank(extendedInformation)) {
            result = JSON.parseObject(extendedInformation);
        }
        return result;
    }

    @Override
    public Boolean updateEmployeeExtendField(EmployeeExtendFieldParam param) {
        Long memberId = param.getEmployeeId();
        String code = param.getCode();
        Object value = param.getValue();
        JSONObject jsonObject = queryEmployeeExtendField(memberId);
        jsonObject.put(code, value);
        EmployeeDO upDo = new EmployeeDO();
        upDo.setId(memberId);
        upDo.setExtendField(jsonObject.toJSONString());
        int count = employeeMapper.updateById(upDo);
        return count > 0;
    }

    @Override
    public void employeeQrCode(Long employeeId, HttpServletResponse response, QrCodeParam param) {
        EmployeeBO employeeBO = getBean().selectById(employeeId);
        if (null == employeeBO) {
            throw new BusinessException("请先在企业微信添加员工");
        }
        //todo 测试静态、动态会员码设置
        Integer qrCodeType = QrCodeTypeEnum.QR_CODE_TYPE_DYNAMIC.getValue();
        String content;
        if (qrCodeType == null || QrCodeTypeEnum.QR_CODE_TYPE_STATIC.equals(qrCodeType)) {
            //静态码 取会员id
            content = employeeId.toString();
        } else {
            //动态码 取uuid
            content = IdGen.uuid();
        }
        QrcodeConfig config = new QrcodeConfig()
                .setBorderSize(2)
                .setPadding(10)
                .setMasterColor("#000000")
                .setCodeEyesPointColor("#000000")
                //.setCodeEyesFormat(QreyesFormat.C_BORDER_C_POINT)
                .setLogoBorderColor("#000000")
                .setLogoRatio(4)
                .setLogoShape(Codectx.LogoShape.CIRCLE);

        try {
            OutputStream os = response.getOutputStream();
            boolean b = new SimpleQrcodeGenerator(config)
                    .setRemoteLogo(employeeBO.getAvatar())
                    .generate(content)
                    .toStream(os);
            if (b) {
                if (qrCodeType == null || QrCodeTypeEnum.QR_CODE_TYPE_STATIC.equals(qrCodeType)) {
                    redisUtils.set(RedisKeyConstant.QR_CODE + content, employeeBO.getId());
                } else {
                    redisUtils.set(RedisKeyConstant.QR_CODE + content, employeeBO.getId(), configProp.getQrCode());
                }
            } else {
                throw new BusinessException("会员码刷新失败，请重试");
            }
        } catch (IOException e) {
            LogUtils.error(LogClassifyEnum.ERROR_LOG, "获取输出会员码流失败:[{}]", e.getMessage());
            throw new BusinessException("获取输出会员码流失败", e);
        }
    }

    /**
     * 通过身份证号获取生日
     *
     * @param identifyNumber
     * @return
     */
    public String getBirtByIdNo(String identifyNumber) {
        int length = StringUtils.length(identifyNumber);
        DataUtils.falseThrowException(length == 15 || length == 18, "请填写有效的身份证号码!");
        String dateOfBirth = null;
        //通过身份证获取性别和生日
        if (identifyNumber.length() == 15) {
            dateOfBirth = "19" + identifyNumber.substring(6, 8) + "-" + identifyNumber.substring(8, 10) + "-" + identifyNumber.substring(10, 12);
        } else if (identifyNumber.length() == 18) {
            dateOfBirth = identifyNumber.substring(6, 10) + "-" + identifyNumber.substring(10, 12) + "-" + identifyNumber.substring(12, 14);
        }
        return dateOfBirth;
    }

    public String getArea(String provinceCode, String cityCode, String regionCode, String streetCode, String flag) {
        flag = org.apache.commons.lang3.StringUtils.isBlank(flag) ? "/" : flag;
        //所在地区
        Set<String> codeSet = new HashSet<>();
        codeSet.add(provinceCode);
        codeSet.add(cityCode);
        codeSet.add(regionCode);
        codeSet.add(streetCode);
        List<AreaDTO> areaDtos = Optional.ofNullable(globalDictFeignClient.queryNames(new ArrayList<>(codeSet))).map(ResponseResult::getData).orElseGet(() -> Collections.EMPTY_LIST);
        Map<String, String> areaMap = areaDtos.stream().collect(Collectors.toMap(AreaDTO::getCode, AreaDTO::getName, (o, n) -> n));
        ArrayList<Object> areaList = CollUtil.newArrayList();
        DataUtils.collectionAdd(areaList, StringUtils.isNotBlank(areaMap.get(provinceCode)), areaMap.get(provinceCode));
        DataUtils.collectionAdd(areaList, StringUtils.isNotBlank(areaMap.get(cityCode)), areaMap.get(cityCode));
        DataUtils.collectionAdd(areaList, StringUtils.isNotBlank(areaMap.get(regionCode)), areaMap.get(regionCode));
        DataUtils.collectionAdd(areaList, StringUtils.isNotBlank(areaMap.get(streetCode)), areaMap.get(streetCode));
        return StringUtils.join(areaList, flag);
    }

    @Override
    public EmployeeVO view(Long id) {
        EmployeeDO entityDO = employeeMapper.selectById(id);
        if(entityDO == null) return new EmployeeVO();
        List<DepartmentDO> departmentDOList = departmentMapper.selectList(new LambdaQueryWrapper<DepartmentDO>().eq(DepartmentDO::getPublishStatus,PublishStatusEnum.ENABLE.getValue()));
        Map<Long, String> departmentNameMaps = Collections3.isNotEmpty(departmentDOList)?departmentDOList.parallelStream().collect(Collectors.toMap(DepartmentDO::getId, DepartmentDO::getName, (o, n) -> o)):null;

        List<OrgPositionDO> orgPositionDOList = orgPositionMapper.selectList(new LambdaQueryWrapper<OrgPositionDO>().eq(OrgPositionDO::getPublishStatus,PublishStatusEnum.ENABLE.getValue()));
        Map<Long, String> orgPositionNameMaps = Collections3.isNotEmpty(orgPositionDOList)?orgPositionDOList.parallelStream().collect(Collectors.toMap(OrgPositionDO::getId, OrgPositionDO::getName, (o, n) -> o)):null;
        Map<Long, Long> orgPositionJobMaps = Collections3.isNotEmpty(orgPositionDOList)?orgPositionDOList.parallelStream().collect(Collectors.toMap(OrgPositionDO::getId, OrgPositionDO::getJobId, (o, n) -> o)):null;

        EmployeeVO entityVO = BeanUtil.convertBeanByJson(entityDO, EmployeeVO.class);
        entityVO.setDepartmentName(departmentNameMaps!=null?departmentNameMaps.get(entityDO.getDepartmentId()):"");
        entityVO.setPositionName(orgPositionNameMaps!=null?orgPositionNameMaps.get(entityDO.getPositionId()):"");
        entityVO.setJobId(orgPositionJobMaps!=null?orgPositionJobMaps.get(entityDO.getPositionId()):null);
        entityVO.setGenderDesc(SexEnum.getDescByCode(entityDO.getGender()));
        entityVO.setStatusDesc(EmployeeStatusEnum.getDescByCode(entityDO.getStatus()));
        return entityVO;
    }

    @Override
    public EmployeeBO selectById(Long id) {
        if (id == null) {
            return null;
        }
        EmployeeDO memberInfoDO = employeeMapper.selectById(id);
        if(StringUtils.isEmpty(memberInfoDO.getAvatar()))
            memberInfoDO.setAvatar(DefaultPathConstant.DEFAULT_USER_HEAD_IMAGE);
        memberInfoDO.setAvatar(UrlUtils.addUrlDomainName(fileOssProp.getHost(),memberInfoDO.getAvatar()));
        return BeanUtil.convertBeanByJson(memberInfoDO, EmployeeBO.class);
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public Boolean changeStatus(Long id, Integer status) {
        EmployeeDO entityDO = employeeMapper.selectById(id);

        entityDO.setStatus(status);
        entityDO.setModifyBy(UserUtils.getUserId());
        entityDO.setModifyTime(LocalDateTime.now());
        return employeeMapper.updateById(entityDO) > 0;
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public Boolean del(Long id) {
        EmployeeDO entityDO = employeeMapper.selectById(id);
        if (entityDO == null) {
            return true;
        }
        PublishStatusEnum.statusCheckException(entityDO.getStatus());
        //删除会员偏好关系表数据
        return employeeMapper.deleteById(id) > 0;
    }

    @Override
    public List<EmployeeDTO> feignQueryEmployeeList(EmployeeFeignQuery query){
        List<EmployeeDTO> resultVOS = new ArrayList<>();
        List<EmployeeDO> entityDOS = employeeMapper.selectList(new LambdaQueryWrapper<EmployeeDO>()
                .eq(query.getId()!=null ,EmployeeDO::getId, query.getId())
                .in(Collections3.isNotEmpty(query.getIds()), EmployeeDO::getId, query.getIds())
                .eq(query.getDepartmentId()!=null ,EmployeeDO::getDepartmentId, query.getDepartmentId())
                .eq(query.getGender()!=null ,EmployeeDO::getGender, query.getGender())
                .eq(StringUtils.isNotEmpty(query.getCode()),EmployeeDO::getCode, query.getCode())
                .like(StringUtils.isNotEmpty(query.getName()),EmployeeDO::getName, query.getName())
                .eq(query.getStatus()!=null ,EmployeeDO::getStatus, query.getStatus())
                .orderByDesc(EmployeeDO::getCreateTime));
        if(Collections3.isNotEmpty(entityDOS)) {
            List<OrgPositionDO> orgPositionDOList = orgPositionMapper.selectList(new LambdaQueryWrapper<OrgPositionDO>().eq(OrgPositionDO::getPublishStatus, PublishStatusEnum.ENABLE.getValue()));
            Map<Long, Long> orgPositionJobMaps = Collections3.isNotEmpty(orgPositionDOList) ? orgPositionDOList.parallelStream().collect(Collectors.toMap(OrgPositionDO::getId, OrgPositionDO::getJobId, (o, n) -> o)) : null;

            resultVOS = entityDOS.stream().map(s -> {
                EmployeeDTO entityDTO = BeanUtil.convertBean(s, EmployeeDTO.class);
                entityDTO.setJobId(orgPositionJobMaps != null ? orgPositionJobMaps.get(s.getPositionId()) : null);
                return entityDTO;
            }).collect(Collectors.toList());
        }
        return resultVOS;
    }
    /**
     * 校验唯一性
     *
     * @param param
     */
    public void checkUnique(EmployeeParam param) {
        if (param == null) {
            throw new BusinessException("当前职位数据不存在!");
        }
        //code name确保等级唯一性
        LambdaQueryWrapper<EmployeeDO> queryWrapper = new LambdaQueryWrapper<EmployeeDO>()
                .ne(param.getId() != null, EmployeeDO::getId, param.getId())
                .eq(EmployeeDO::getName, param.getName());
        List<EmployeeDO> dos = employeeMapper.selectList(queryWrapper);
        if (Collections3.isNotEmpty(dos)) {
            throw new BusinessException("已经存在同名的职位!");
        }
    }

    private List<Long> getAllDepartmentIdsByPId(Long parentId){
        List<Long> departmentIdS = new ArrayList<>();
        departmentIdS.add(parentId);
        List<DepartmentDO> allDepartmentList = departmentMapper.selectList(new LambdaQueryWrapper<>(DepartmentDO.class).eq(DepartmentDO::getPublishStatus,PublishStatusEnum.ENABLE.getValue()));
        List<DepartmentTreeVO> allDepartmentTrees = JsonUtils.jsonToList(allDepartmentList, DepartmentTreeVO.class);
        List<Long> result = new ArrayList<>();
        TreeFastUtils.selectLongCidByPid(result, allDepartmentTrees, departmentIdS);
        result.addAll(departmentIdS);
        return result;
    }

    @Override
    public List<EmployeeStatusVO> employeeStatusList() {
        List<EmployeeStatusVO> result = new ArrayList<>();
        EmployeeStatusVO statusVO = null;
        for (EmployeeStatusEnum application : EmployeeStatusEnum.values()) {
            statusVO = new EmployeeStatusVO();
            statusVO.setCode(application.getCode());
            statusVO.setDesc(application.getDesc());
            result.add(statusVO);
        }
        return result;
    }

    private static IEmployeeService getBean() {
        return SpringBeanUtil.getBean(IEmployeeService.class);
    }

}